export const draggable = {
  bind(el) {
    let placeholder;
    let isDragging = false;
    let offsetX = 0;
    let offsetY = 0;
    let left = 0;
    let top = 0;
    let requestId = null;

    const onMouseDown = (event) => {
      // console.log("event.target:", event.target);
      // console.log("el:", el);
      const isDraggableChild =
        event.target === el ||
        getComputedStyle(event.target).cursor === 'move';
      // console.log("onMouseDown1", isDraggableChild);
      // 如果点击的不是可拖拽元素本身，不阻止默认行为和冒泡
      if (event.target !== el && !isDraggableChild) {
        return;
      }
      // console.log("onMouseDown2");
      // 阻止事件冒泡
      event.stopPropagation();
      // 阻止默认的文本选择行为
      event.preventDefault();
      isDragging = true;
      // 获取元素的初始位置和尺寸
      const rect = el.getBoundingClientRect();
      left = rect.left;
      top = rect.top;
      offsetX = event.clientX - left;
      offsetY = event.clientY - top;

      // 获取元素的定位方式
      const computedStyle = getComputedStyle(el);
      const position = computedStyle.position;

      // 如果元素是绝对定位，不创建占位元素
      if (position === "absolute") {
        placeholder = null;
      } else {
        // 如果占位元素存在，将其从文档中移除
        if (placeholder) {
          placeholder.parentNode.removeChild(placeholder);
          placeholder = null;
        }

        // 获取原元素影响空间的 CSS 值
        const marginLeft = computedStyle.marginLeft;
        const marginTop = computedStyle.marginTop;
        const marginRight = computedStyle.marginRight;
        const marginBottom = computedStyle.marginBottom;
        const paddingLeft = computedStyle.paddingLeft;
        const paddingTop = computedStyle.paddingTop;
        const paddingRight = computedStyle.paddingRight;
        const paddingBottom = computedStyle.paddingBottom;
        const borderLeftWidth = computedStyle.borderLeftWidth;
        const borderTopWidth = computedStyle.borderTopWidth;
        const borderRightWidth = computedStyle.borderRightWidth;
        const borderBottomWidth = computedStyle.borderBottomWidth;

        // 获取元素的实际宽高
        const width = rect.width;
        const height = rect.height;

        // 创建占位元素
        placeholder = document.createElement("div");
        placeholder.style.width = `${width}px`;
        placeholder.style.height = `${height}px`;
        placeholder.style.visibility = "hidden";
        // 应用影响空间的 CSS 值到占位元素
        placeholder.style.margin = `${marginTop} ${marginRight} ${marginBottom} ${marginLeft}`;
        placeholder.style.padding = `${paddingTop} ${paddingRight} ${paddingBottom} ${paddingLeft}`;
        placeholder.style.borderWidth = `${borderTopWidth} ${borderRightWidth} ${borderBottomWidth} ${borderLeftWidth}`;
        placeholder.style.borderStyle = "solid";

        el.parentNode.insertBefore(placeholder, el);
      }

      // 设置元素为绝对定位，使其可以自由移动
      el.style.position = "absolute";
      // 应用实际宽高
      el.style.width = `${rect.width}px`;
      el.style.height = `${rect.height}px`;
      el.style.left = `${left}px`;
      el.style.top = `${top}px`;
      el.style.transition = "none";
      const maxZIndex = getMaxZIndex();
      el.style.zIndex = maxZIndex + 1;

      // 在捕获阶段添加 mousemove 和 mouseup 事件监听器
      document.addEventListener("mousemove", onMouseMove, { capture: true });
      document.addEventListener("mouseup", onMouseUp, { capture: true });
    };
    const getMaxZIndex = () => {
      return Array.from(document.querySelectorAll('body *'))
        .map(el => parseInt(window.getComputedStyle(el).zIndex) || 0)
        .reduce((max, zIndex) => Math.max(max, zIndex), 0);
    }
    const onMouseMove = (event) => {
      // 阻止事件冒泡
      event.stopPropagation();
      // 阻止默认的文本选择行为
      event.preventDefault();
      if (isDragging) {
        if (!requestId) {
          requestId = requestAnimationFrame(() => {
            left = event.clientX - offsetX;
            top = event.clientY - offsetY;
            el.style.left = `${left}px`;
            el.style.top = `${top}px`;
            requestId = null;
          });
        }
      }
    };

    const onMouseUp = (event) => {
      // 阻止事件冒泡
      event.stopPropagation();
      // 阻止默认的文本选择行为
      event.preventDefault();
      isDragging = false;
      el.style.transition = "left 0.2s ease, top 0.2s ease";
      // 在捕获阶段移除 mousemove 和 mouseup 事件监听器
      document.removeEventListener("mousemove", onMouseMove, { capture: true });
      document.removeEventListener("mouseup", onMouseUp, { capture: true });
      if (requestId) {
        cancelAnimationFrame(requestId);
        requestId = null;
      }
      // 不再移除占位元素
    };

    const onMouseOver = (event) => {
      if (event.target === el) {
        el.style.cursor = "move";
      } else {
        el.style.cursor = "default";
      }
    };

    // 添加指令销毁时的清理逻辑
    const destroy = () => {
      el.removeEventListener('mousedown', onMouseDown);
      el.removeEventListener('mouseover', onMouseOver);
      if (placeholder && placeholder.parentNode) {
        placeholder.parentNode.removeChild(placeholder);
      }
    };

    // 保存销毁函数以便unbind时调用
    el._draggableDestroy = destroy;

    el.addEventListener("mousedown", onMouseDown);
    el.addEventListener("mouseover", onMouseOver);
  },
  unbind(el) {
    // 执行清理
    if (el._draggableDestroy) {
      el._draggableDestroy();
      delete el._draggableDestroy;
    }
  }
};

export const draggableChild = {
  bind(el) {
    // console.log("draggableChild bind called on element:", el);
    // 向上查找最近的draggable父元素
    const findDraggableParent = (element) => {
      let parent = element.parentElement;
      while (parent) {
        if (parent.hasAttribute('v-draggable') ||
          parent.__vue__?.$options?.directives?.draggable) {
          return true;
        }
        parent = parent.parentElement;
      }
      return false;
    };

    if (!findDraggableParent(el)) {
      // console.warn('[Vue warn]: v-draggable-child must be used inside a v-draggable element');
    }

    // 设置鼠标样式
    el.style.cursor = 'move';
  },

  unbind(el) {
    // 清理样式
    el.style.cursor = '';
  }
};
